﻿using Common.Library;
using Common.Model;
using Container.Library;
using Dapper.Library;
using DevOps.Model;
using Serialize.Library;
using System;
using System.Collections.Generic;
using System.Linq;

/*
* 命名空间: DevOps.Logic
*
* 功 能： 菜单功能管理
*
* 类 名： FunctionCfgServiceImpl
*
* Version   变更日期            负责人     变更内容
* ─────────────────────────────────────────────────
* V1.0.1    2020/03/124 14:34:43 Harvey     创建
*
* Copyright (c) 2020 Harvey Corporation. All rights reserved.
*/
namespace DevOps.Logic
{
    /// <summary>
    /// 菜单功能管理
    /// </summary>
    public class FunctionCfgServiceImpl : OperationLogicImpl, IFunctionCfgService
    {

        #region 主界面菜单逻辑方法【运维平台和其他平台公用】

        /// <summary>
        /// 获取【用户】对应应用的可操作的菜单信息
        /// </summary>
        /// <param name="appSecret">应用appSecret</param>
        /// <returns></returns>
        public ResultJsonInfo<List<MenuInfo>> LoadMenuOfUserList(string appSecret)
        {
            var resultInfo = new ResultJsonInfo<List<MenuInfo>>();
            List<MenuInfo> listInfo = new List<MenuInfo>();
            //获取用户登录信息
            var user = GetLoginUserInfo();

            if (!string.IsNullOrEmpty(appSecret))
            {
                using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
                {
                    con.Transaction(tran =>
                    {
                        var appInfo = tran.QuerySet<SafeApplicationInfoEntity>().Where(p => p.appsecret.Equals(appSecret)).Get();

                        if (appInfo != null)
                        {
                            //如果是超级管理员，就直接获取相应系统所有可操作菜单
                            if (user.is_super_user)
                            {
                                var functionListInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                              .Where(p => p.is_deleted == false && p.is_valid == true)
                                                              .OrderBy(p => p.sort).ToList();

                                if (functionListInfo.Count > 0)
                                {
                                    //可操作菜单，放redis中
                                    FunctionCfgServiceRedis.SaveFunctionCfgOfUser(user.name, functionListInfo);
                                    var menusList = functionListInfo.MapToList<FunctionCfgInfoResponse>();
                                    listInfo = GetFunctionChildTreeInfo(menusList.FindAll(p => p.application_ids.Contains(appInfo.id)), "");
                                }
                            }
                            else
                            {
                                //可操作菜单，redis中获取
                                FunctionCfgServiceRedis.GetFunctionCfgOfUser(user.name,
                                (menusInfo) =>
                                {
                                    var functionListInfo = menusInfo.FindAll(p => p.application_ids.Contains(appInfo.id));
                                    var menusList = functionListInfo.MapToList<FunctionCfgInfoResponse>();
                                    listInfo = GetFunctionChildTreeInfo(menusList, "");
                                },
                                //如果Redis中没有保存信息，只有从数据库中再次获取一次，并保存Redis
                                () =>
                                {
                                    var roleIds = user.role_ids.Split(',').ToArray();
                                    //权限类型
                                    int permissionType = (int)PermissionType.Function;

                                    var functionIds = tran.QuerySet<SysRolePermissionReEntity>()
                                        .Where(p => p.role_id.In(roleIds) && p.permission_type.Equals(permissionType))
                                        .ToList().Select(p => p.permission_id)
                                        .ToArray();

                                    if (functionIds.Length > 0)
                                    {
                                        var functionListInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                                .Where(p => p.is_deleted == false && p.is_valid == true && p.id.In(functionIds))
                                                                .OrderBy(p => p.sort).ToList();

                                        if (functionListInfo.Count > 0)
                                        {
                                            //可操作菜单，放redis中
                                            FunctionCfgServiceRedis.SaveFunctionCfgOfUser(user.name, functionListInfo);
                                            var menusList = functionListInfo.MapToList<FunctionCfgInfoResponse>();
                                            listInfo = GetFunctionChildTreeInfo(menusList.FindAll(p => p.application_ids.Contains(appInfo.id)), "");
                                        }
                                    }
                                });
                            }
                        }
                    });

                    if (listInfo.Count > 0)
                    {
                        resultInfo.Code = ActionCodes.Success;
                        resultInfo.Data = listInfo;
                        resultInfo.Msg = "获取成功！";
                    }
                    else
                    {
                        resultInfo.Msg = "获取用户对应应用的可操作的菜单失败！";
                    }
                }
            }
            else
            {
                resultInfo.Msg = "应用appSecret不能为空！";
            }
            return resultInfo;
        }

        /// <summary>
        /// 获取【用户】对应系统的可操作的菜单信息
        /// </summary>
        /// <param name="appSecret">应用appSecret</param>
        /// <param name="level">层级级别 0：所有 10：一级 20：二级 30：三级</param>
        /// <returns></returns>
        public ResultJsonInfo<List<SysFunctionCfgEntity>> LoadTopMenuOfUserList(string appSecret, int level)
        {
            var resultInfo = new ResultJsonInfo<List<SysFunctionCfgEntity>>();

            //获取用户登录信息
            var user = GetLoginUserInfo();

            List<SysFunctionCfgEntity> listInfo = null;
            string applicationId = string.Empty;

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {
                    var appInfo = tran.QuerySet<SafeApplicationInfoEntity>().Where(p => p.appsecret.Equals(appSecret)).Get();
                    if (appInfo != null)
                    {
                        applicationId = appInfo.id;

                        //如果是超级管理员，就直接获取相应系统所有可操作菜单
                        if (user.is_super_user)
                        {
                            listInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                     .Where(p => p.is_deleted.Equals(false)
                                                             && p.is_valid.Equals(true))
                                                     .OrderBy(p => p.sort)
                                                     .ToList();
                        }
                        else
                        {
                            var roleIds = user.role_ids.Split(',').ToArray();
                            var functionIds = tran.QuerySet<SysRolePermissionReEntity>()
                                .Where(p => p.role_id.In(roleIds))
                                .ToList().Select(p => p.permission_id)
                                .ToArray();

                            if (functionIds.Length > 0)
                            {
                                listInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                      .Where(p => p.is_deleted.Equals(false)
                                                              && p.is_valid.Equals(true)
                                                              && p.id.In(functionIds))
                                                      .OrderBy(p => p.sort)
                                                      .ToList();
                            }
                        }
                    }
                });
                if (listInfo.Count > 0)
                {
                    //可操作菜单，放redis中
                    FunctionCfgServiceRedis.SaveFunctionCfgOfUser(user.name, listInfo);

                    resultInfo.Code = ActionCodes.Success;
                    if (level == 0)
                    {
                        resultInfo.Data = listInfo.FindAll(p => p.application_ids.Contains(applicationId));
                    }
                    else
                    {
                        resultInfo.Data = listInfo.FindAll(p => p.application_ids.Contains(applicationId) && p.level == level);
                    }
                    resultInfo.Msg = "获取成功！";
                }
                else
                {
                    resultInfo.Msg = "获取顶级菜单信息失败！";
                }
            }

            return resultInfo;
        }

        /// <summary>
        /// 获取用户对应系统的可操作的一级菜单信息【ExtraInfo返回pathname对应一级菜单节点ID】---暂时废弃
        /// </summary>
        /// <param name="appSecret">应用appSecret</param>
        /// <param name="pathname">子节点相对地址</param>
        /// <param name="level">层级级别 0：所有 10：一级 20：二级 30：三级</param>
        /// <returns></returns>
        public ResultJsonInfo<List<SysFunctionCfgEntity>> LoadTopMenuOfUserList(string appSecret, string pathname, int level)
        {
            var resultInfo = new ResultJsonInfo<List<SysFunctionCfgEntity>>();

            //获取用户登录信息
            var user = GetLoginUserInfo();

            List<SysFunctionCfgEntity> listInfo = null;
            string applicationId = string.Empty;

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {
                    var appInfo = tran.QuerySet<SafeApplicationInfoEntity>().Where(p => p.appsecret.Equals(appSecret)).Get();
                    if (appInfo != null)
                    {
                        applicationId = appInfo.id;

                        //如果是超级管理员，就直接获取相应系统所有可操作菜单
                        if (user.is_super_user)
                        {
                            listInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                     .Where(p => p.is_deleted.Equals(false)
                                                             && p.is_valid.Equals(true))
                                                     .OrderBy(p => p.sort)
                                                     .ToList();
                        }
                        else
                        {
                            var roleIds = user.role_ids.Split(',').ToArray();
                            var functionIds = tran.QuerySet<SysRolePermissionReEntity>()
                                .Where(p => p.role_id.In(roleIds))
                                .ToList().Select(p => p.permission_id)
                                .ToArray();

                            if (functionIds.Length > 0)
                            {
                                listInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                      .Where(p => p.is_deleted.Equals(false)
                                                              && p.is_valid.Equals(true)
                                                              && p.id.In(functionIds))
                                                      .OrderBy(p => p.sort)
                                                      .ToList();
                            }
                        }
                    }
                });
                if (listInfo.Count > 0)
                {
                    //可操作菜单，放redis中
                    FunctionCfgServiceRedis.SaveFunctionCfgOfUser(user.name, listInfo);

                    resultInfo.Code = ActionCodes.Success;

                    if (level == 0)
                    {
                        resultInfo.Data = listInfo.FindAll(p => p.application_ids.Contains(applicationId));
                    }
                    else
                    {
                        resultInfo.Data = listInfo.FindAll(p => p.application_ids.Contains(applicationId) && p.level == level);
                    }
                    var itemInfo = listInfo.Find(p => p.link_url.Equals(pathname));
                    if (itemInfo != null)
                    {
                        resultInfo.ExtraInfo = listInfo.GetParentInfo(itemInfo.id).id;
                    }
                    resultInfo.Msg = "获取成功！";
                }
                else
                {
                    resultInfo.Msg = "获取失败！";
                }
            }
            return resultInfo;
        }

        /// <summary>
        /// 获取【用户拥有的】左侧二级或三级菜单信息
        /// </summary>
        /// <param name="appSecret">应用appSecret</param>
        /// <param name="parentId"></param>
        /// <returns></returns>
        public ResultJsonInfo<List<MenuInfo>> LoadSubMenus(string appSecret, string parentId)
        {
            var resultInfo = new ResultJsonInfo<List<MenuInfo>>();
            List<MenuInfo> listInfo = new List<MenuInfo>();
            //获取用户登录信息
            var user = GetLoginUserInfo();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {
                    var appInfo = tran.QuerySet<SafeApplicationInfoEntity>().Where(p => p.appsecret.Equals(appSecret)).Get();
                    if (appInfo != null)
                    {
                        //如果是超级管理员，就直接获取相应系统所有可操作菜单
                        if (user.is_super_user)
                        {
                            var functionListInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                          .Where(p => p.is_deleted.Equals(false) && p.is_valid.Equals(true))
                                                          .OrderBy(p => p.sort).ToList();

                            if (functionListInfo.Count > 0)
                            {
                                //可操作菜单，放redis中
                                FunctionCfgServiceRedis.SaveFunctionCfgOfUser(user.name, functionListInfo);
                                var menusList = functionListInfo.MapToList<FunctionCfgInfoResponse>();
                                listInfo = GetFunctionChildTreeInfo(menusList.FindAll(p => p.application_ids.Contains(appInfo.id)), parentId);
                            }
                        }
                        else
                        {
                            //可操作菜单，redis中获取
                            FunctionCfgServiceRedis.GetFunctionCfgOfUser(user.name,
                           (menusInfo) =>
                           {
                               var functionListInfo = menusInfo.FindAll(p => p.application_ids.Contains(appInfo.id));
                               var menusList = functionListInfo.MapToList<FunctionCfgInfoResponse>();
                               listInfo = GetFunctionChildTreeInfo(menusList, parentId);
                           },
                           //如果Redis中没有保存信息，只有从数据库中再次获取一次，并保存Redis
                           () =>
                           {
                               var roleIds = user.role_ids.Split(',').ToArray();
                               var functionIds = tran.QuerySet<SysRolePermissionReEntity>()
                                   .Where(p => p.role_id.In(roleIds))
                                   .ToList().Select(p => p.permission_id)
                                   .ToArray();
                               if (functionIds.Length > 0)
                               {
                                   var functionListInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                           .Where(p => p.is_deleted.Equals(false) && p.is_valid.Equals(true) && p.id.In(functionIds))
                                                           .OrderBy(p => p.sort).ToList();

                                   if (functionListInfo.Count > 0)
                                   {
                                       //可操作菜单，放redis中
                                       FunctionCfgServiceRedis.SaveFunctionCfgOfUser(user.name, functionListInfo);

                                       var menusList = functionListInfo.MapToList<FunctionCfgInfoResponse>();
                                       listInfo = GetFunctionChildTreeInfo(menusList.FindAll(p => p.application_ids.Contains(appInfo.id)), parentId);
                                   }
                               }
                           });
                        }
                    }
                });
            }
            if (listInfo.Count > 0)
            {
                resultInfo.Code = ActionCodes.Success;
                resultInfo.Data = listInfo;
                resultInfo.Msg = "获取成功！";
            }
            else
            {
                resultInfo.Msg = "获取二级或三级菜单失败！";
            }
            return resultInfo;
        }

        /// <summary>
        /// 获取用户可以操作的第一个菜单界面
        /// </summary>
        /// <param name="userInfo"></param>
        /// <param name="appSecret"></param>
        /// <returns></returns>
        public string LoadFirstMenuOfUser(UserLoginInfo userInfo, string appSecret)
        {
            string result = string.Empty;

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {
                    var appInfo = tran.QuerySet<SafeApplicationInfoEntity>().Where(p => p.appsecret.Equals(appSecret)).Get();

                    if (appInfo != null)
                    {

                        List<SysFunctionCfgEntity> functionListInfo = new List<SysFunctionCfgEntity>();
                        //如果是超级管理员，就直接获取相应系统所有可操作菜单
                        if (userInfo.is_super_user)
                        {
                            functionListInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                          .Where(p => p.is_deleted == false && p.is_valid == true && p.application_ids.Contains(appInfo.id))
                                                          .OrderBy(p => p.sort).ToList();
                        }
                        else
                        {
                            var roleIds = userInfo.role_ids.Split(',').ToArray();
                            //权限类型
                            int permissionType = (int)PermissionType.Function;

                            var functionIds = tran.QuerySet<SysRolePermissionReEntity>()
                                .Where(p => p.role_id.In(roleIds) && p.permission_type.Equals(permissionType))
                                .ToList().Select(p => p.permission_id)
                                .ToArray();

                            if (functionIds.Length > 0)
                            {
                                functionListInfo = tran.QuerySet<SysFunctionCfgEntity>()
                                                        .Where(p => p.is_deleted == false && p.is_valid == true && p.id.In(functionIds))
                                                        .OrderBy(p => p.sort).ToList();
                            }
                        }
                        if (functionListInfo.Count > 0)
                        {
                            //function类型 
                            string functionType = ((int)FunctionType.Menu).ToString();
                            var functionInfo = functionListInfo.FindAll(p => p.function_type.Equals(functionType)).FirstOrDefault();
                            if (functionInfo != null)
                            {
                                result = functionInfo.link_url;
                            }
                        }
                    }
                });
            }

            return result;
        }

        #endregion

        #region 菜单基础信息管理

        #region 查询

        /// <summary>
        /// 根据菜单名称或系统类型获取菜单列表信息
        /// </summary>
        /// <param name="queryInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<List<FunctionCfgInfoResponse>> LoadListInfo(ParametersInfo<FunctionCfgQueryRequest> queryInfo)
        {
            var resultInfo = new ResultJsonInfo<List<FunctionCfgInfoResponse>>();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                var result = con.QuerySet<SysFunctionCfgEntity>();

                if (queryInfo.parameters != null)
                {
                    if (queryInfo.parameters.application_id.IsNotNullOrEmpty())
                    {
                        result.Where(p => p.application_ids.Contains(queryInfo.parameters.application_id));
                    }
                    if (queryInfo.parameters.name.IsNotNullOrEmpty())
                    {
                        result.Where(p => p.name.Contains(queryInfo.parameters.name));
                    }
                }

                var functionListInfo = result.Where(p => p.is_deleted == false)
                                  .OrderBy(p => p.sort).PageList(queryInfo.page, queryInfo.limit);

                if (functionListInfo.Items.Count > 0)
                {
                    var menusList = functionListInfo.Items.MapToList<FunctionCfgInfoResponse>();

                    //这里获取所有，查询是否有兄弟节点
                    var functionListInfoAll = result.Where(p => p.is_deleted == false)
                         .OrderBy(p => p.sort).ToList();
                    foreach (var item in menusList)
                    {
                        //NET算术运算溢出问题
                        item.have_elder = functionListInfoAll.Exists(p => p.sort < item.sort && p.level == item.level && p.id != item.id && p.parent_id == item.parent_id);
                        item.have_younger = functionListInfoAll.Exists(p => p.sort > item.sort && p.level == item.level && p.id != item.id && p.parent_id == item.parent_id);
                    }
                    resultInfo.Code = ActionCodes.Success;
                    resultInfo.Data = menusList;
                    resultInfo.Count = functionListInfo.Total;
                    resultInfo.Msg = "获取成功！";
                }
                else
                {
                    resultInfo.Msg = "无对应数据！";
                    resultInfo.Data = new List<FunctionCfgInfoResponse>();
                }
            }

            return resultInfo;
        }

        /// <summary>
        /// 根据菜单名称或系统类型获取菜单树状列表信息
        /// </summary>
        /// <param name="queryInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<List<MenuInfo>> LoadTreeListInfo(FunctionCfgQueryRequest queryInfo)
        {
            var resultInfo = new ResultJsonInfo<List<MenuInfo>>();

            List<FunctionCfgInfoResponse> listInfo = new List<FunctionCfgInfoResponse>();
            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                var result = con.QuerySet<SysFunctionCfgEntity>();

                //这里获取所有，查询是否有兄弟节点
                var listInfoAll = result.Where(p => p.is_deleted == false).OrderBy(p => p.sort).ToList();

                if (queryInfo.application_id.IsNotNullOrEmpty())
                {
                    result.Where(p => p.application_ids == queryInfo.application_id);
                }
                if (queryInfo.name.IsNotNullOrEmpty())
                {
                    result.Where(p => p.name.Contains(queryInfo.name));
                }
                var queryList = result.Where(p => p.is_deleted == false)
                                  .OrderBy(p => p.sort).ToList();


                var queryInfoRes = queryList.MapToList<FunctionCfgInfoResponse>();

                foreach (var item in queryInfoRes)
                {
                    //NET算术运算溢出问题
                    item.have_elder = listInfoAll.Exists(p => p.sort < item.sort && p.level == item.level && p.id != item.id && p.parent_id == item.parent_id);
                    item.have_younger = listInfoAll.Exists(p => p.sort > item.sort && p.level == item.level && p.id != item.id && p.parent_id == item.parent_id);
                }
                //所有信息
                var listInfoAllRes = listInfoAll.MapToList<FunctionCfgInfoResponse>();


                if (queryInfo.name.IsNotNullOrEmpty())
                {
                    if (queryInfoRes.Count > 0)
                    {
                        for (int i = 0; i < queryInfoRes.Count; i++)
                        {
                            QueryParent(listInfoAllRes, queryInfoRes[i].id, ref listInfo);
                            QueryChildren(listInfoAllRes, queryInfoRes[0].id, ref listInfo);
                        }
                        queryInfoRes = listInfo;
                    }
                }
                if (queryInfoRes.Count > 0)
                {
                    resultInfo.Code = ActionCodes.Success;
                    resultInfo.Data = GetFunctionChildTreeInfo(queryInfoRes, "");
                    resultInfo.Msg = "获取成功！";
                }
                else
                {
                    resultInfo.Msg = "获取菜单树状列表信息失败！";
                }
            }
            return resultInfo;
        }


        /// <summary>
        /// 向上查询父级数据
        /// </summary>
        /// <param name="list">ALL</param>
        /// <param name="id"></param>
        /// <param name="resultList"></param>
        private void QueryParent(List<FunctionCfgInfoResponse> list, string id, ref List<FunctionCfgInfoResponse> resultList)
        {
            var info = list.Where(a => a.id == id).ToList();
            if (info.Count > 0)
            {
                resultList.Add(info[0]);
                if (info[0].parent_id != "" && info[0].parent_id != null)
                {
                    QueryParent(list, info[0].parent_id, ref resultList);
                }
            }
        }

        /// <summary>
        /// 向下查询子级数据
        /// </summary>
        /// <param name="list"></param>
        /// <param name="id"></param>
        /// <param name="resultList"></param>
        private void QueryChildren(List<FunctionCfgInfoResponse> list, string id, ref List<FunctionCfgInfoResponse> resultList)
        {

            var info = list.Where(a => a.id == id).ToList();
            if (info.Count > 0)
            {
                var xia = list.Where(a => a.parent_id == info[0].id).ToList();
                for (int i = 0; i < xia.Count; i++)
                {
                    resultList.Add(xia[i]);
                    QueryChildren(list, xia[i].id, ref resultList);
                }
            }
        }
        #endregion

        #region 更新

        /// <summary>
        /// 新增节点信息
        /// </summary>
        /// <param name="inputInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<int> AddInfo(FunctionCfgAddRequest inputInfo)
        {
            var resultInfo = new ResultJsonInfo<int>();

            var user = GetLoginUserInfo();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                var result = 0;
                var sysFunctionCfg = inputInfo.MapTo<SysFunctionCfgEntity>();

                if (inputInfo.parent_id.IsNotNullOrEmpty())
                {
                    con.Transaction(tran =>
                    {
                        var allFunction = tran.QuerySet<SysFunctionCfgEntity>().ToList();//.Where(p => p.is_deleted == false)

                        var sysMenuInfo = allFunction.Find(p => p.id == inputInfo.parent_id);

                        if (sysMenuInfo != null)
                        {
                            //查询出排序在该节点之后的所有节点
                            var sysDepartmentInfos = allFunction.FindAll(p => p.sort > sysMenuInfo.sort);
                            foreach (var item in sysDepartmentInfos)
                            {
                                item.sort = item.sort + 1;
                                tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                            }
                            //插入数据
                            sysFunctionCfg.id = GuidHelper.GetGuid();
                            sysFunctionCfg.sort = sysMenuInfo.sort + 1;
                            sysFunctionCfg.level = sysMenuInfo.level + 10;
                            sysFunctionCfg.creator_id = user.id;
                            sysFunctionCfg.creator_name = user.name;
                            sysFunctionCfg.modifier_id = user.id;
                            sysFunctionCfg.modifier_name = user.name;
                            result = tran.CommandSet<SysFunctionCfgEntity>().Insert(sysFunctionCfg);

                            if (result > 0)
                            {
                                resultInfo.Code = ActionCodes.Success;
                                resultInfo.Data = result;
                                resultInfo.Msg = "新增子节点信息成功！";
                                AddOperationLog(OperationLogType.AddOperation, BusinessTitleType.FunctionManage, $"新增子节点信息:{JsonHelper.ToJson(sysFunctionCfg)}");
                            }
                            else
                            {
                                resultInfo.Msg = "操作失败！";
                            }
                            //int count = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.name == sysFunctionCfg.name).Count();
                            //if (count == 0)
                            //{
                            //}
                            //else
                            //{
                            //    resultInfo.Msg = "菜单名重复！";
                            //}
                        }
                        else
                        {
                            resultInfo.Msg = "无对应父节点信息！";
                        }
                    });
                }
                else
                {
                    con.Transaction(tran =>
                    {

                        //获取所有菜单信息
                        var maxSort = con.QuerySet<SysFunctionCfgEntity>().Max(p => p.sort);
                        sysFunctionCfg.id = GuidHelper.GetGuid();
                        sysFunctionCfg.sort = maxSort + 1;
                        sysFunctionCfg.level = (int)MenuLevel.First;
                        sysFunctionCfg.creator_id = user.id;
                        sysFunctionCfg.creator_name = user.name;
                        sysFunctionCfg.modifier_id = user.id;
                        sysFunctionCfg.modifier_name = user.name;

                        result = con.CommandSet<SysFunctionCfgEntity>().Insert(sysFunctionCfg);
                        if (result > 0)
                        {
                            resultInfo.Code = ActionCodes.Success;
                            resultInfo.Data = result;
                            resultInfo.Msg = "新增节点信息成功！";
                            AddOperationLog(OperationLogType.AddOperation, BusinessTitleType.FunctionManage, $"新增根节点信息:{JsonHelper.ToJson(sysFunctionCfg)}");
                        }
                        else
                        {
                            resultInfo.Msg = "新增节点信息失败！";
                        }

                        //int count = con.QuerySet<SysFunctionCfgEntity>().Where(p => p.name == sysFunctionCfg.name).Count();
                        //if (count == 0)
                        //{

                        //}
                        //else
                        //{
                        //    resultInfo.Msg = "菜单名重复！";
                        //}
                    });
                }
            }
            return resultInfo;
        }

        /// <summary>
        /// 修改节点信息
        /// </summary>
        /// <param name="modifyInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<int> Modify(FunctionCfgModifyRequest modifyInfo)
        {

            var resultInfo = new ResultJsonInfo<int>();
            var sysMenu = modifyInfo.MapTo<SysFunctionCfgEntity>();
            var user = GetLoginUserInfo();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                var result = 0;
                con.Transaction(tran =>
                {
                    var sysFunctionCfg = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.id == sysMenu.id).Get();
                    if (sysFunctionCfg != null)
                    {
                        sysFunctionCfg.name = sysMenu.name;
                        sysFunctionCfg.application_ids = modifyInfo.application_ids;
                        sysFunctionCfg.application_name = modifyInfo.application_name;
                        sysFunctionCfg.function_type = modifyInfo.function_type;
                        sysFunctionCfg.describe = modifyInfo.describe;
                        sysFunctionCfg.icon_font = sysMenu.icon_font;
                        sysFunctionCfg.link_url = sysMenu.link_url;
                        sysFunctionCfg.is_valid = sysMenu.is_valid;
                        sysFunctionCfg.modifier_id = user.id;
                        sysFunctionCfg.modifier_name = user.name;


                        result = tran.CommandSet<SysFunctionCfgEntity>().Update(sysFunctionCfg);
                        if (result > 0)
                        {
                            //修改时，如果是禁用菜单。。需要将它的子菜单一起禁用
                            if (sysMenu.is_valid == false)
                            {
                                var listInfo = new List<SysFunctionCfgEntity>();
                                var allInfo = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.is_deleted == false).ToList();
                                var rootInfo = allInfo.FindAll(p => p.name.Contains(sysMenu.name));
                                if (rootInfo.Count > 0)
                                {
                                    listInfo.AddRange(rootInfo);
                                    listInfo.AddRange(allInfo.GetChildList(rootInfo));
                                }
                                foreach (var item in listInfo)
                                {
                                    item.is_valid = false;
                                    tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                                }
                            }
                        }
                        //var exists = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.id != modifyInfo.id && p.name == modifyInfo.name).Count();
                        //if (exists == 0)
                        //{
                        //}
                        //else
                        //{
                        //    resultInfo.Msg = "菜单名称重复！";
                        //}
                    }
                    else
                    {
                        resultInfo.Msg = "无对应菜单信息！";
                    }
                });
                if (result > 0)
                {
                    resultInfo.Code = ActionCodes.Success;
                    resultInfo.Data = result;
                    resultInfo.Msg = "修改菜单信息成功！";
                    AddOperationLog(OperationLogType.ModifyOperation, BusinessTitleType.FunctionManage, $"修改节点信息成功，节点信息：{JsonHelper.ToJson(modifyInfo)}");
                }
                else
                {
                    resultInfo.Msg = "操作失败,请检查菜单名称是否重复！";
                }
            }
            return resultInfo;
        }

        /// <summary>
        /// 移动顺序操作
        /// </summary>
        /// <param name="inputInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<int> MoveSort(FunctionCfgMoveRequest inputInfo)
        {

            var result = new ResultJsonInfo<int>();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {
                    //（1）所有功能
                    var adminFuns = tran.QuerySet<SysFunctionCfgEntity>().OrderBy(p => p.sort).ToList();//.Where(p => p.is_deleted == false)

                    //（2）当前功能 
                    SysFunctionCfgEntity currAdminFun = adminFuns.Find(p => p.id == inputInfo.id);

                    //（3）当前功能兄弟节点
                    List<SysFunctionCfgEntity> brothersAdminFun = adminFuns.FindAll(p => p.parent_id == currAdminFun.parent_id);

                    SysFunctionCfgEntity broAdminFun = null;

                    foreach (SysFunctionCfgEntity item in brothersAdminFun)
                    {
                        if (inputInfo.flag == 1)//上移
                        {
                            if (item.sort < currAdminFun.sort) { broAdminFun = item; }
                            if (item.sort > currAdminFun.sort) { break; } //找到上一个兄弟节点
                        }
                        else //下移
                        {
                            if (item.sort > currAdminFun.sort) { broAdminFun = item; break; } //找到下一个兄弟节点
                        }
                    }

                    List<SysFunctionCfgEntity> currFuns = new List<SysFunctionCfgEntity>();
                    currFuns.Add(currAdminFun);
                    GetMoveNode(adminFuns, currAdminFun.id, currFuns);

                    List<SysFunctionCfgEntity> moveFuns = new List<SysFunctionCfgEntity>();
                    moveFuns.Add(broAdminFun);
                    GetMoveNode(adminFuns, broAdminFun.id, moveFuns);

                    //上移
                    if (inputInfo.flag == 1)
                    {
                        foreach (SysFunctionCfgEntity item in currFuns)
                        {
                            item.sort = short.Parse((item.sort - short.Parse(moveFuns.Count.ToString())).ToString());
                            tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                        }

                        foreach (SysFunctionCfgEntity item in moveFuns)
                        {
                            item.sort = short.Parse((item.sort + short.Parse(currFuns.Count.ToString())).ToString());
                            tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                        }
                    }
                    else
                    {
                        foreach (SysFunctionCfgEntity item in currFuns)
                        {
                            item.sort = short.Parse((item.sort + short.Parse(moveFuns.Count.ToString())).ToString());
                            tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                        }
                        foreach (SysFunctionCfgEntity item in moveFuns)
                        {
                            item.sort = short.Parse((item.sort - short.Parse(currFuns.Count.ToString())).ToString());
                            tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                        }
                    }
                });
                result.Code = ActionCodes.Success;
                result.Data = 1;
            }
            return result;
        }

        /// <summary>
        /// 上下一定子功能（递归）
        /// </summary>
        /// <param name="adminFuns"></param>
        /// <param name="funId"></param>
        /// <param name="move"></param>
        private void GetMoveNode(List<SysFunctionCfgEntity> adminFuns, string funId, List<SysFunctionCfgEntity> move)
        {
            List<SysFunctionCfgEntity> borgs = adminFuns.FindAll(r => r.parent_id == funId);
            foreach (SysFunctionCfgEntity item in borgs)
            {
                if (item.parent_id == funId)
                {
                    move.Add(item);
                    List<SysFunctionCfgEntity> tempFuns = adminFuns.FindAll(r => r.parent_id == item.id);
                    if (tempFuns != null && tempFuns.Count > 0)
                    {
                        GetMoveNode(adminFuns, item.id, move);
                    }
                }
            }
        }

        /// <summary>
        /// 菜单启用与停用操作
        /// </summary>
        /// <param name="id"></param>
        /// <returns></returns>
        public ResultJsonInfo<int> ForbiddenInfo(string id)
        {

            var resultInfo = new ResultJsonInfo<int>();

            var user = GetLoginUserInfo();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {

                    var infoList = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.id == id || p.parent_id == id).ToList();

                    if (infoList != null && infoList.Count > 0)
                    {
                        var info = infoList.Find(p => p.id == id);
                        if (info.is_valid)
                        {
                            info.is_valid = !info.is_valid;
                            info.modifier_date = DateTime.Now;
                            info.modifier_id = user.id;
                            info.modifier_name = user.name;
                            tran.CommandSet<SysFunctionCfgEntity>().Update(info);

                            infoList = infoList.Where(a => a.id != id).ToList();
                            foreach (var item in infoList)
                            {
                                if (item.is_valid)
                                {
                                    item.is_valid = false;
                                }
                                item.modifier_date = DateTime.Now;
                                item.modifier_id = user.id;
                                item.modifier_name = user.name;
                                tran.CommandSet<SysFunctionCfgEntity>().Update(item);
                            }
                        }
                        else
                        {
                            if (info.is_valid)
                            {
                                info.is_valid = false;
                            }
                            else
                            {
                                info.is_valid = true;
                            }
                            tran.CommandSet<SysFunctionCfgEntity>().Update(info);
                        }
                        resultInfo.Code = ActionCodes.Success;
                        resultInfo.Msg = "操作成功！";
                        AddOperationLog(OperationLogType.ModifyOperation, BusinessTitleType.FunctionManage, $"禁用/启用菜单成功，禁用/启用菜单信息：{JsonHelper.ToJson(id)}");

                    }
                    else
                    {
                        resultInfo.Code = ActionCodes.ArgumentInvalid;
                        resultInfo.Msg = "id无效！";
                    }
                });
            }
            return resultInfo;
        }

        /// <summary>
        /// 删除节点
        /// </summary>
        /// <param name="ids"></param>
        /// <returns></returns>
        public ResultJsonInfo<int> Remove(string[] ids)
        {

            var resultInfo = new ResultJsonInfo<int>();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {

                    var result = 0;
                    if (ids.Length >= 0)
                    {
                        var listInfo = new List<SysFunctionCfgEntity>();
                        var allInfo = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.is_deleted == false).ToList();
                        var rootInfo = allInfo.FindAll(p => ids.Contains(p.id));
                        if (rootInfo.Count > 0)
                        {
                            listInfo.AddRange(rootInfo);
                            listInfo.AddRange(allInfo.GetChildList(rootInfo));
                        }
                        var listCode = listInfo.Select(p => p.id).ToArray();

                        //查看是否被角色使用，如果没使用，可以删除
                        var roleMenuCount = tran.QuerySet<SysRolePermissionReEntity>().Where(p => p.id.In(listCode)).Count();
                        if (roleMenuCount == 0)
                        {
                            //逻辑删除菜单
                            result = tran.CommandSet<SysFunctionCfgEntity>().Where(p => p.id.In(listCode))
                                        .Update(a =>
                                            new SysFunctionCfgEntity
                                            {
                                                is_deleted = true
                                            });

                            if (result > 0)
                            {
                                resultInfo.Code = ActionCodes.Success;
                                resultInfo.Data = result;
                                resultInfo.Msg = "操作成功！";

                                AddOperationLog(OperationLogType.ModifyOperation, BusinessTitleType.FunctionManage, $"删除节点成功，删除节点ID信息：{JsonHelper.ToJson(ids)}");
                            }
                            else
                            {
                                resultInfo.Msg = "操作失败！";
                            }
                        }
                        else
                        {
                            resultInfo.Msg = "选中菜单已被角色已使用，无法删除！";
                        }
                    }
                    else
                    {
                        resultInfo.Msg = "id为空，操作失败！";
                    }
                });
            }
            return resultInfo;
        }
        #endregion

        #endregion

        #region 权限配置相关

        /// <summary>
        /// 根据角色ID，获取所有可操作菜单已赋权限情况
        /// </summary>
        /// <param name="queryInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<List<FunctionCfgRoleMenuResponse>> LoadListInfoByRoleId(FunctionCfgRoleQuery queryInfo)
        {
            var resultInfo = new ResultJsonInfo<List<FunctionCfgRoleMenuResponse>>();

            var menusList = new List<FunctionCfgRoleMenuResponse>();

            List<SysFunctionCfgEntity> listInfo = null;
            List<SysRolePermissionReEntity> sysRoleMenu = null;

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {

                con.Transaction(tran =>
                {

                    listInfo = tran.QuerySet<SysFunctionCfgEntity>()
                              .Where(p => p.is_deleted == false && p.is_valid == true)
                              .OrderBy(p => p.sort)
                              .ToList();

                    int permissionType = (int)PermissionType.Function;
                    sysRoleMenu = tran.QuerySet<SysRolePermissionReEntity>()
                        .Join<SysRolePermissionReEntity, SysFunctionCfgEntity>((a, b) => a.permission_id == b.id)
                        .From<SysRolePermissionReEntity, SysFunctionCfgEntity>()
                        .OrderBy<SysFunctionCfgEntity>(p => p.sort)
                        .Where((a, b) => a.permission_type.Equals(permissionType) && b.is_valid.Equals(true) && a.role_id.Equals(queryInfo.roleId))
                        .ToList((a, b) => new SysRolePermissionReEntity
                        {
                            id = a.id,
                            role_id = a.role_id,
                            permission_id = a.permission_id,
                            permission_type = a.permission_type
                        });

                    menusList = listInfo.MapToList<FunctionCfgRoleMenuResponse>();

                    foreach (var item in menusList)
                    {
                        if (sysRoleMenu.Exists(p => p.permission_id == item.id))
                        {
                            item.lay_is_checked = true;
                        }
                    }
                });
            }

            if (listInfo.Count > 0)
            {
                resultInfo.Code = ActionCodes.Success;
                resultInfo.Data = menusList;
                resultInfo.Count = menusList.Count;
                resultInfo.Msg = "获取成功！";
            }
            else
            {
                resultInfo.Msg = "无对应信息！";
            }
            return resultInfo;
        }

        /// <summary>
        /// 根据角色ID，获取所有可操作菜单已赋权限情况
        /// </summary>
        /// <param name="queryInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<List<MenuTreeInfo>> LoadTreeListByRoleId(FunctionCfgRoleQuery queryInfo)
        {

            var resultInfo = new ResultJsonInfo<List<MenuTreeInfo>>();
            var treeInfo = new List<MenuTreeInfo>();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {

                con.Transaction(tran =>
                {

                    var listInfo = tran.QuerySet<SysFunctionCfgEntity>()
                               .Where(p => p.is_deleted == false && p.is_valid == true)
                               .OrderBy(p => p.sort)
                               .ToList();

                    int permissionType = (int)PermissionType.Function;
                    var sysRoleMenu = tran.QuerySet<SysRolePermissionReEntity>()
                        .Join<SysRolePermissionReEntity, SysFunctionCfgEntity>((a, b) => a.permission_id == b.id)
                        .From<SysRolePermissionReEntity, SysFunctionCfgEntity>()
                        .OrderBy<SysFunctionCfgEntity>(p => p.sort)
                        .Where((a, b) => a.permission_type.Equals(permissionType) && b.is_valid.Equals(true) && a.role_id.Equals(queryInfo.roleId))
                        .ToList((a, b) => new SysRolePermissionReEntity
                        {
                            id = a.id,
                            role_id = a.role_id,
                            permission_id = a.permission_id,
                            permission_type = a.permission_type
                        });

                    var menusList = listInfo.MapToList<FunctionCfgRoleMenuResponse>();

                    foreach (var item in menusList)
                    {
                        if (sysRoleMenu.Exists(p => p.permission_id == item.id))
                        {
                            item.lay_is_checked = true;
                        }
                    }

                    treeInfo = GetFunctionChildTreeInfo(menusList, "");
                });
            }

            if (treeInfo.Count > 0)
            {
                resultInfo.Code = ActionCodes.Success;
                resultInfo.Data = treeInfo;
                resultInfo.Msg = "获取成功！";
            }
            else
            {
                resultInfo.Msg = "无对应信息！";
            }
            return resultInfo;
        }

        /// <summary>
        /// 修改对应角色赋值的菜单操作权限
        /// </summary>
        /// <param name="modifyInfo"></param>
        /// <returns></returns>
        public ResultJsonInfo<int> ModifyRoleMenuInfo(FunctionCfgRoleModifyRequest modifyInfo)
        {
            var resultInfo = new ResultJsonInfo<int>();

            using (var con = DataBase.GetConnection(DatabaseName.Sql_BUS_DB.ToString()))
            {
                con.Transaction(tran =>
                {
                    var menuCodes = modifyInfo.menuIdList;

                    #region 获取当前选中节点和选中节点的子节点
                    var allInfo = tran.QuerySet<SysFunctionCfgEntity>().Where(p => p.is_deleted == false && p.is_valid == true)
                                                                .OrderBy(p => p.sort)
                                                                .ToList();
                    var rootInfo = allInfo.FindAll(p => menuCodes.Contains(p.id));

                    var listInfo = new List<SysFunctionCfgEntity>();
                    if (rootInfo.Count > 0)
                    {
                        listInfo.AddRange(rootInfo);
                        listInfo.AddRange(allInfo.GetParentList(rootInfo));
                    }
                    menuCodes = listInfo.Select(t => t.id).Distinct().ToList();

                    #endregion

                    //获取该角色原有的菜单权限
                    int permissionType = (int)PermissionType.Function;
                    var roleMenuListInfo = tran.QuerySet<SysRolePermissionReEntity>()
                                    .Where(p => p.role_id.Equals(modifyInfo.roleid) && p.permission_type.Equals(permissionType))
                                    .ToList();

                    //1、获取需要删除的，删除掉。
                    var needRemoveRoleMenuListInfo = roleMenuListInfo.FindAll(p => !menuCodes.Contains(p.permission_id))
                                    .Select(p => p.permission_id)
                                    .ToArray();

                    if (needRemoveRoleMenuListInfo.Length > 0)
                    {
                        //删除掉不用的菜单
                        tran.CommandSet<SysRolePermissionReEntity>()
                                        .Where(p => p.permission_id.In(needRemoveRoleMenuListInfo) && p.role_id.Equals(modifyInfo.roleid))
                                        .Delete();
                    }

                    //2、获取需要增加的，增加上。
                    var needAddRoleMenuListInfo = menuCodes.ToList()
                                    .FindAll(p => !roleMenuListInfo.Select(roleMenu => roleMenu.permission_id).Contains(p));

                    SysRolePermissionReEntity roleMenuItem = null;
                    foreach (var item in needAddRoleMenuListInfo)
                    {
                        roleMenuItem = new SysRolePermissionReEntity();
                        roleMenuItem.id = GuidHelper.GetGuid();
                        roleMenuItem.role_id = modifyInfo.roleid;
                        roleMenuItem.permission_id = item;
                        roleMenuItem.permission_type = (int)PermissionType.Function;
                        tran.CommandSet<SysRolePermissionReEntity>().Insert(roleMenuItem);
                    }
                    resultInfo.Code = ActionCodes.Success;
                    resultInfo.Data = 1;
                    resultInfo.Msg = "操作成功！";
                });
            }
            return resultInfo;
        }

        #endregion

        #region 公用功能

        /// <summary>
        /// 获取功能类型Select列表信息
        /// </summary>
        /// <returns></returns>
        public ResultJsonInfo<List<EnumToSelectItem>> LoadFunctionTypeList()
        {

            var resultInfo = new ResultJsonInfo<List<EnumToSelectItem>>();
            resultInfo.Data = EnumToSelectItem.GetEnumDescriptionList(typeof(FunctionType), true);
            resultInfo.Code = ActionCodes.Success;
            resultInfo.Msg = "获取成功！";

            return resultInfo;
        }

        #endregion
    }
}
